package com.heima.article.service;

import cn.hutool.core.collection.CollectionUtil;
import com.alibaba.fastjson.JSON;
import com.fasterxml.jackson.databind.util.BeanUtil;
import com.heima.article.constants.ArticleConstants;
import com.heima.article.mapper.ApArticleMapper;
import com.heima.common.cache.CacheService;
import com.heima.model.article.pojos.ApArticle;
import com.heima.model.article.vos.HotArticleVo;
import com.sun.org.apache.bcel.internal.generic.IF_ACMPEQ;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;

import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.Comparator;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

/**
 * @author 大可
 * @date 2022/7/29 11:30
 */
@Service
public class HotArticleServiceImpl implements HotArticleService {

    @Autowired
    private ApArticleMapper apArticleMapper;

    @Autowired
    private CacheService cacheService;

    @Override
    public void computehotArticle() {
        //查询五天内文章
        LocalDateTime date = LocalDateTime.now().minusDays(5);
        List<ApArticle> articleByLast5days = apArticleMapper.findArticleListByLast5days(date);
        if (CollectionUtils.isEmpty(articleByLast5days)) {
            return;
        }
        //计算分值
        List<HotArticleVo> hotArticleVos = computeScore(articleByLast5days);
        if (CollectionUtils.isEmpty(hotArticleVos)){
            return;
        }
        //分组缓存
        gropAndCache(hotArticleVos);
    }

    private void gropAndCache(List<HotArticleVo> hotArticleVos){
        //按频道分组
        List<List<HotArticleVo>> listGroupByChannel = CollectionUtil.groupByField(hotArticleVos,"channelId");
        if (CollectionUtil.isEmpty(listGroupByChannel)){
            return;
        }
        for (List<HotArticleVo> list : listGroupByChannel) {
            if (CollectionUtil.isEmpty(list)){
                return;
            }
            Integer channelId = list.get(0).getChannelId();
            sortedAndCache(list,ArticleConstants.LOADTYPE_LOAD_MORE + channelId.toString());
        }
        //推荐分一组
        sortedAndCache(hotArticleVos,ArticleConstants.LOADTYPE_LOAD_MORE + ArticleConstants.DEFAULT_TAG);
    }

    private void sortedAndCache(List<HotArticleVo> hotArticleVos,String key){
        if (CollectionUtils.isEmpty(hotArticleVos)){
            return;
        }
        hotArticleVos = hotArticleVos.stream().sorted(Comparator.comparing(HotArticleVo::getScore).reversed().reversed()).collect(Collectors.toList());
        //截取30条
        if (hotArticleVos.size() > 30){
            hotArticleVos = hotArticleVos.subList(0,30);
        }
        cacheService.set(key, JSON.toJSONString(hotArticleVos));
    }

    private List<HotArticleVo> computeScore(List<ApArticle> list) {
        if (CollectionUtils.isEmpty(list)) {
            return new ArrayList<>();
        }
        List<HotArticleVo> voList = new ArrayList<>();
        for (ApArticle apArticle : list) {
            if (apArticle == null) {
                continue;
            }
            //计算得分
            HotArticleVo vo = compute(apArticle);
            if (vo == null) {
                continue;
            }
            voList.add(vo);
        }
        return voList;
    }

    private HotArticleVo compute(ApArticle apArticle) {
        if (apArticle == null) {
            return null;
        }
        Integer comment = apArticle.getComment();
        Integer likes = apArticle.getLikes();
        Integer views = apArticle.getViews();
        Integer collection = apArticle.getCollection();

        Integer score = 0;

        if (comment != null) {
            score += comment;
        }
        if (likes != null) {
            score += likes * 3;
        }
        if (views != null) {
            score += views * 5;
        }
        if (collection != null) {
            score += collection * 8;
        }
        HotArticleVo vo = new HotArticleVo();
        BeanUtils.copyProperties(apArticle,vo);
        vo.setScore(score);
        return vo;
    }

}
